<?php
/**
 *  NevuxBB - Free Forum Software
 *  Copyright (C) 2008, 2010 NevuxBB (No one specific author)*  This program is free software: you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation, either version 3 of the License, or
 *  (at your option) any later version.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *
 *  You should have received a copy of the GNU General Public License
 *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
 *
 * MySQL Database Class
 * File: Db_Abstraction.php
 * Purpose: Access the MySQL Database and run queries.
 * Todo: Add more functionality, finish error handling
 *
 */
 
class Db_Abstraction {
	static $mysql_query_count;
	static $mysql_query_array = Array();
	
	/**
	 * Connects to the Mysql database
	 *
	 * @param string $cfg     Array used for mysql login information
	 * @return void
	 * @access public
	 */
	public function connect($cfg) {
		$conn = mysql_connect($cfg['dbhost'], $cfg['dbuser'], $cfg['dbpass']);
		if(!$conn) {
			trigger_error('Unable to communicate with the database server, check if it\'s down or password protected.', E_USER_ERROR);
		}
		
		if(!mysql_select_db($cfg['dbname'], $conn)) {
			trigger_error('Unable to select the database, does it actually exist?', E_USER_ERROR);
	 	}
		
		// should this be counted?
		#self::update_query_count();
 	}
	
	/**
	 * Array's data from a mysql expression result
	 *
	 * @param string $query  The query inserted into the function
	 * @return string $result	Returns fetched data in an array
	 * @access public
	 */	
	public function fetch_array($query) {
		$query_catch = $query;
		$query = mysql_query($query) or die(Db_Abstraction::error('Mysql Query Failed', mysql_error()));
		
		self::$mysql_query_count++;
		self::$mysql_query_array[] = "fetch_array() - ".$query_catch;
		
		return @mysql_fetch_array($query);
		
		// clear memory
		mysql_free_result($query);
	}
	
	 /**
	 * Query's the database
	 *
	 * @param string $query	  The query inserted into the function
	 * @return string $result	Returns query
	 * @access public
	 */	
	public function query($query, $return_id = NULL){
		$result = mysql_query($query) or die(Db_Abstraction::error('Mysql Query Failed', mysql_error()));
		$result_id = mysql_insert_id();
		
		// increment query counter
		self::$mysql_query_count++;
		self::$mysql_query_array[] = "query() - ".$query;
		
		// do we return id?
		if($return_id) {
			return $result_id;
		} else {
			return $result;
		}
		
		// clear memory
		mysql_free_result($query);
	}
	
	public function num_rows($object) {
		// how many rows
		$rows = mysql_num_rows($object);
		
		// return number of rows
		return $rows;
	}
	
	 /**
	 * Fetch's data from the database
	 *
	 * @param string $query	  The query inserted into the function
	 * @param string $no_error  (optional) Tells function not to return errors if set to '0'
	 * @return string $value	Returns result
	 * @access public
	 */		 
	public function fetch($query, $no_error = 1) {
		if($no_error == 0) {
			$result = mysql_fetch_array($query);
		} else {
			$result = mysql_fetch_array($query) or die(Db_Abstraction::error('Mysql Fetch Array Failed', mysql_error()));
		}
		
		self::$mysql_query_count++;
		self::$mysql_query_array[] = "fetch() - ".$query;
		return $result;
		
		// clear memory
		mysql_free_result($query);
	}
	
	/**
	 * Fetch's data from the database
	 *
	 * @param string $query	  The query inserted into the function
	 * @param string $no_error  (optional) Tells function not to return errors if set to '0'
	 * @return string $value	Returns result
	 * @access public
	 */		 
	public function fetch_assoc($result) {
		// return the required function
		return mysql_fetch_assoc($result);
		
		// clear memory
		mysql_free_result($result);
	}
	
	 /**
	 * Insert data into the database
	 *
	 * Usage:
	 * <code>
	 * 			$data = array(
	 *				'row_name' => "data", 
	 *				'row_name2' => "more data" 
	 *				);	
     *
     *			Db_Abstraction::insert( 'table_name', $data );
	 * </code>
	 *
	 * @param string $table	  The table being used for insertation
	 * @param string $data 	  The data being inserted into the database, using an array
	 * @return string true    Returns true
	 * @access public
	 */	
	public function insert($table, $data) {
		$fields = implode(array_keys($data), ',');
		$values = "'" . implode(array_values($data), "','") . "'";
		$query = "INSERT INTO " . $table . " (" . $fields . ") VALUES (" . $values . ")";
		Db_Abstraction::query($query);
		
		self::$mysql_query_count++;
		return true;
		
		// clear memory
		mysql_free_result($query);
	}

	 /**
	 * Updates database with new data
	 *
	 * Usage:
	 * <code>
	 * 			$data = array(
	 *				'row_name' => "data", 
	 *				'row_name2' => "more data" 
	 *				);	
	 *
	 *			Db_Abstraction::update( 'table_name', $data, "entry = '2'" );
	 * </code>
	 *
	 * @param string $table	  The table being updated
	 * @param string $data 	  The data being updated to the database, using an array
	 * @param string $where   The row matching this result
	 * @return string true    Returns true
	 * @access public
	 */		 
	public function update($table, $data, $where) {
		$query = "UPDATE " . $table . " SET ";
		foreach($data as $var => $value) {
			if($i>0) {
				$query .= ", ";
			}
			
			$query .= $var . " = '" . $value . "'";
			$i++;
		}
		
		$query .=" WHERE " . $where . " LIMIT 1;";
		Db_Abstraction::query($query);
		
		self::$mysql_query_count++;
		return true;
		
		// clear memory
		mysql_free_result($query);
	}
	
	 /**
	 * Delete data from the database
	 *
	 * Usage:
	 * <code>
	 * 			$data = $_POST['delete'];
	 *			Where 'delete' is an array from a form
	 *
	 *			Db_Abstraction::delete( 'table_name', $data, 'column_name' );
	 * </code>
	 *
	 * @param string $table	  The table being used for row deletion
	 * @param string $data 	  The data value to match the deletion query
	 * @param string $where	  The column to match the $data value to
	 * @return string true    Returns true
	 * @access public
	 */	
	public function delete($table, $data, $where) {
		foreach ($data as $delete) {
			$query = "DELETE FROM " . $table . " WHERE " . $where . " =" . $delete . " LIMIT 1";
			Db_Abstraction::query( $query );
		}
		
		self::$mysql_query_count++;
		return true;
		
		// clear memory
		mysql_free_result($query);
	}
	
	
	/**
	 * Secure the GET inputs
	 *
	 * @param String $value  The GET input
	 * @return $value	     Returns $value
	 */ 
	public function clean($value) {
		// Stripslashes
		$phpver = explode('-', phpversion());
		if($phpver[0] < '6.0.0') {
			if (get_magic_quotes_gpc()) {
				$value = stripslashes($value);
			}
		}
   
		// Quote if not integer
		if (!is_numeric($value) || $value[0] == '0') {
			$value = mysql_real_escape_string($value);
		}
		
		return $value;
	} 
	
	
	/**
	 * Displays an error when a mysql expression fails
	 *
	 * @param String $title Title of the error
	 * @param String $msg	Message in the error
	 * @return mixed	Returns error details
	 */ 	
	private function error($title, $msg) {
		echo('<div>
		    	<h2 style="color: red;">' . $title . '</h2>
		    	<p>' . $msg . '</p>
		      </div>');
	}
	
	/**
	 * Returns numerically all the queries done
	 *
	 * @return numeric	Number
	 */ 	
	public function get_total_queries() {
		// return the total queries
		return self::$mysql_query_count;
	}
	
	/**
	 * Returns all the queries done
	 *
	 * @return mixed	Array
	 */ 	
	public function get_total_queries_array() {
		// return the total queries
		return self::$mysql_query_array;
		unset(self::$mysql_query_array);
	}
}	

?>